package com.fengwk.resource.service.impl;

import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;

import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import org.springframework.beans.factory.annotation.Autowired;
//import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;

import com.fengwk.resource.face.constant.ResourceConstant;
import com.fengwk.resource.face.entity.ResFile;
import com.fengwk.resource.face.model.File;
import com.fengwk.resource.service.FileService;
import com.fengwk.resource.service.UploadService;
import com.fengwk.support.code.Sequence;
import com.fengwk.support.exception.BaseException;
import com.fengwk.support.util.ArrayUtils;
import com.fengwk.support.util.CodeUtils;
import com.fengwk.support.util.DateUtils;
import com.fengwk.support.util.FileExtensionUtils;
import com.fengwk.support.util.FileUtils;
import com.fengwk.support.util.StringUtils;
import com.fengwk.support.util.ThumbnailatorUtils;
import com.fengwk.support.util.WebUtils;

/**
 * 本地存储
 * {@link GitUploadServiceImpl}
 * 
 * @author fengwk
 *
 */
//@Service
public class UploadServiceImpl implements UploadService {
	
	private static final String IMG_SIZE_SPLIT = "*";
		
	@Autowired
	private FileService fileService;
	
	@Transactional
	@Override
	public List<File> files(Long userId, HttpServletRequest request) throws IOException {
		List<ResFile> rfList = new ArrayList<>();
		MultipartHttpServletRequest multiRequest = (MultipartHttpServletRequest) request;
		// 获取multiRequest中所有的文件名
		Iterator<String> it = multiRequest.getFileNames();
		while (it.hasNext()) {
			MultipartFile multipartFile = multiRequest.getFile(it.next().toString());
			if (multipartFile != null) {
				// 文件序号
				Long fileId = Sequence.next();
				
				// 文件名称和类型
				String name = multipartFile.getOriginalFilename();
				String type = null;
				
				// 获取文件后缀
				String[] typeSplit = FileExtensionUtils.split(name);
				if(ArrayUtils.isNotBlank(typeSplit))
					type = typeSplit[1];
				
				// 获取文件尺寸,占用大小
				String size = null;
				Long length = null;
				
				// 文件相对路径和绝对路径
				String relativePath = null;
				String absolutePath = null;
				
				Long serverId = null;
				
				// 文件md5摘要
				String md5 = CodeUtils.md5Hex(multipartFile.getBytes());
				ResFile sameMd5File = fileService.getLastByMd5(md5);
				if (sameMd5File == null) {
					// 之前不存在的文件
					// 绝对路径
					String dateFolderPath = WebUtils.SEPARATOR + DateUtils.current(DateUtils.YYYYMMDD);
					String preAbsolutePath = ResourceConstant.PRE_FILE_ABSOLUTE_PATH + dateFolderPath;
					
					// 最后一级
					String saveUriPath = WebUtils.SEPARATOR + fileId;
					if (StringUtils.isNotBlank(type))
						saveUriPath += FileExtensionUtils.EXTENTSION_CHARACTER + type;
					
					absolutePath = preAbsolutePath + saveUriPath;
					relativePath = dateFolderPath + saveUriPath;
					
					java.io.File file = FileUtils.buildFile(absolutePath, true);
					multipartFile.transferTo(file);
					
					if(!file.exists())
						throw new BaseException("上传文件为空或解析拷贝异常");
						
					length = file.length();
					
					// 若文件为图片则生成缩略图
					if(fileService.shouldThumbnail(type)) {
						// 添加缩略图后缀
						String saveThumbnailPath = preAbsolutePath + WebUtils.SEPARATOR + fileId + ResourceConstant.THUMBNAIL_SUFFIX;
						if (StringUtils.isNotBlank(type))
							saveThumbnailPath += FileExtensionUtils.EXTENTSION_CHARACTER + type;
						ThumbnailatorUtils.thumbnail(absolutePath, saveThumbnailPath, ResourceConstant.THUMBNAIL_QUALITY);
						BufferedImage bi = ImageIO.read(new java.io.File(absolutePath));
						size = bi.getWidth() + IMG_SIZE_SPLIT + bi.getHeight();
					}
				} else {
					// 已存在文件,重新存储一个副本
					size = sameMd5File.getSize();
					length = sameMd5File.getLength();
					relativePath = sameMd5File.getRelativePath();
					absolutePath = sameMd5File.getAbsolutePath();
					serverId = sameMd5File.getServerId();
				}
				ResFile rf = fileService.save(fileId, name, type, size, length, relativePath, absolutePath, userId, md5, serverId, null);
				rfList.add(rf);
			}
		}
		
		return fileService.toFileList(rfList);
	}

	@Override
	public List<File> urls(Long userId, Collection<String> urls) {
		// TODO Auto-generated method stub
		return null;
	}

}
